#ifndef HASIO_IO_CONTEXT_HPP
#define HASIO_IO_CONTEXT_HPP

#if defined(_MSC_VER) && (_MSC_VER >= 1200)
# pragma once
#endif // defined(_MSC_VER) && (_MSC_VER >= 1200)

#include "detail/scheduler.hpp"

namespace hasio {
namespace detail {
using io_context_impl = scheduler;
}

template<typename Initiation, 
    typename Handler,
    typename... Args>
void async_initiate(Initiation initiation, Handler handler, Args... args)
{
    initiation(handler, args...);
}

class io_context
{
public:
    io_context()
        : impl_(add_impl(new impl_type()))
    {}
    ~io_context() {}
private:
    using impl_type = detail::io_context_impl;

public:
    struct initiate_post;

    void run()
    {
        impl_.run();
    }

    void dispatch()
    {

    }

    template<typename Handler>
    void post(Handler handler)
    {
        async_initiate(initiate_post(), handler, this);
    }

private:
    impl_type& add_impl(impl_type* impl)
    {
        return *impl;
    }

    template <typename Service>
    friend Service& use_service(io_context &ioc);

    impl_type& impl_;
};

}

#include "impl/io_context.hpp"

#endif // HASIO_IO_CONTEXT_HPP 